
function loadHighScores()
	result = {}
	for i=1,5 do
		local nameInt = pmem(i-1)
		local i1 = nameInt % 32
		local i2 = math.floor(nameInt / 32) % 32
		local i3 = math.floor(nameInt / 1024) % 32
		local score = pmem(i)
		if (score ~= 0) then
			table.insert(result, {
				name = {numToChar(i1), numToChar(i2), numToChar(i3)},
				score = score
			})
		end
	end
	highScores = result
	sortHighScores()
end

function saveHighScores()
	sortHighScores()
	for i=1,5 do
		if (highScores[i] ~= nil) then
			local i1 = charToNum(highScores[i].name[1])
			local i2 = charToNum(highScores[i].name[2])
			local i3 = charToNum(highScores[i].name[3])
			local nameInt = i3 * 1024 + i2 * 32 + i1
			pmem(i-1, nameInt)
			pmem(i, highScores[i].score)
		end
	end
end

function renderHighScoreEntry()
	if (newHighScore == nil) then return end

	print(newHighScore.name[1], 100, 50, 12)
	print(newHighScore.name[2], 110, 50, 12)
	print(newHighScore.name[3], 120, 50, 12)
	print(newHighScore.score, 150, 50, 12)
	print("OK", 110, 100, 12)

	if (newHighScore.y == 1) then
		if (newHighScore.x == 1) then
			print("_", 100, 54, 12)
		elseif (newHighScore.x == 2) then
			print("_", 110, 54, 12)
		else
			print("_", 120, 54, 12)
		end
	else
		print("_", 110, 104, 12)
	end
end

function printPopUpBackground(stackAmount)
	local iMax = 26
	local jMax = 13
	for i=1,iMax do
		for j=1,jMax do
			local sprKey
			if (i == 1 and j == 1) then
				sprKey = 432
			elseif (i == 1 and j == jMax) then
				sprKey = 464
			elseif (i == iMax and j == 1) then
				sprKey = 434
			elseif (i == iMax and j == jMax) then
				sprKey = 466
			elseif (i == 1) then
				sprKey = 448
			elseif (j == 1) then
				sprKey = 433
			elseif (i == iMax) then
				sprKey = 450
			elseif (j == jMax) then
				sprKey = 465
			else
				sprKey = 449
			end
			spr(sprKey, i*8 + stackAmount * 4 - 4, j*8 + stackAmount * 4 - 4)
		end
	end
end

function getCommoditySprite(code)
	if (code >= 1 and code <= 8) then
		return 2 * code + 254
	else
		return 2 * code + 270
	end
end

function getPlanetSprite(code)
	return code + 435
end

function renderPage(pageId)
	if (page == nil or newHighScore ~= nil) then return end

	local lrArrowHeight
	if (page.level == 1) then
		lrArrowHeight = 114
	elseif (page.level == 2) then
		lrArrowHeight = 104
	else
		lrArrowHeight = 94
	end

	spr(481, 40, lrArrowHeight, 0, 1, 0, 0, 1, 1)
	spr(480, 54, lrArrowHeight, 0, 1, 0, 0, 1, 1)
	spr(480, 160, lrArrowHeight, 0, 1, 1, 0, 1, 1)

	local maxOptions = #page.options
	for i=maxOptions, 1, -1 do
		local optionList = page.options[i]
		if (i == 1) then
			print(optionList[page.selections[i]], 68, 116, 12)
		elseif (i == 2) then
			print(optionList[page.selections[i]], 68, 106, 12)
		elseif (i == 3) then
			print(optionList[page.selections[i]], 68, 96, 12)
		end
	end

	if (warp == nil) then
		print("Planet: " .. player.planet.name, 150, 10, 12)
	end

	if (page.id == "Commodities") then
		local commodityId = getSelection(page, 3)
		local commodity = commodityList[commodityId]
		print("Stock: " .. player.planet.commodities[commodityId], 10, 10, 12)
		print("Unit Cost: " .. math.floor(player.planet.commodityRates[commodityId] * commodity.baseCost), 10, 20, 12)
		print("In Inventory: " .. player.commodities[commodityId], 10, 30, 12)
		print("Credits: " .. string.format("%d", math.floor(player.credits)), 10, 40, 12)
		spr(getCommoditySprite(commodity.code), 138, 60, 0, 1, 0, 0, 2, 2)
	elseif (page.id == "Planets") then
		local id = getSelection(page, 3)
		local targetPlanet = planetList[id]
		local distance = calculatePlanetDistance(player.planet, targetPlanet)
		print("Distance: " .. string.format("%d", math.ceil(distance)) .. "m Miles", 10, 10, 12)
		print("Fuel: " .. tostring(player.ship.fuel) .. " / " .. tostring(player.ship.maxFuel), 10, 20, 12)
		print("Fuel Cost: " .. string.format("%d", math.ceil(distance / 10)), 10, 30, 12)
		
		for i, planetId in ipairs(getNeighbors(player.planet.name)) do
			local relativeX1, relativeY1 = getDistortedRelativeCoordinates(player.planet, sun)
			local relativeX2, relativeY2 = getDistortedRelativeCoordinates(planetList[planetId], sun)
			line(108 + math.floor(relativeX1), 52 - math.floor(relativeY1), 108 + math.floor(relativeX2), 52 - math.floor(relativeY2), 12)
		end
		spr(getPlanetSprite(0), 104, 48, 0, 1, 0, 0, 1, 1)
		for i, planet in ipairs(planetList) do
			local relativeX, relativeY = getDistortedRelativeCoordinates(planet, sun)
			if (relativeX > -112 and relativeX < 112 and relativeY > -28 and relativeY < 28) then
				spr(getPlanetSprite(planet.code), 104 + math.floor(relativeX), 48 - math.floor(relativeY), 0, 1, 0, 0, 1, 1)
			end
			if (targetPlanet == planet) then
				spr(447, 104 + math.floor(relativeX), 48 - math.floor(relativeY), 0, 1, 0, 0, 1, 1)
			end
		end
	elseif (page.id == "Services") then
		local serviceId = getSelection(page, 2)
		local serviceCost = serviceList[serviceId].cost
		print("Hull Condition: " .. string.format("%d", math.floor(100 * player.ship.hullHealth / player.ship.hullStrength)) .. "%", 10, 10, 12)
		print("Fuel: " .. tostring(player.ship.fuel) .. " / " .. tostring(player.ship.maxFuel), 10, 20, 12)
		print("Service Cost: " .. tostring(serviceCost), 10, 30, 12)
		print("Credits: " .. string.format("%d", math.floor(player.credits)), 10, 40, 12)
	elseif (page.id == "Shipyard") then
		local shipId = getSelection(page, 3)
		local ship = shipList[shipId]
		local cost = shipList[shipId].cost
		local tradeInCredit = shipResaleFactor * player.ship.cost
		print("Current ship: " .. player.ship.model, 10, 10, 12)
		print("Current ship trade-in credit: " .. string.format("%d", tradeInCredit), 10, 20, 12)
		print("New ship cost: " .. string.format("%d", cost), 10, 30, 12)
		if (tradeInCredit - cost <= 0) then
			print("Total cost: " .. string.format("%d", cost - tradeInCredit), 10, 40, 12)
		else
			print("Total credit: " .. string.format("%d", tradeInCredit - cost), 10, 40, 12)
		end
		print("Credits: " .. player.credits, 10, 50, 12)
	elseif (page.id == "Pirate Encounter" or page.id == "Cop Encounter" and warp ~= nil) then
		local intDistance = 10 * (warp.maxIters - warp.iter + 1)
		print("Distance to destination: " .. string.format("%d", intDistance) .. "m Miles", 10, 10, 12)
		print("Hull Condition: " .. string.format("%d", math.floor(100 * player.ship.hullHealth / player.ship.hullStrength)) .. "%", 10, 20, 12)
		print("Surrender Cost: " .. string.format("%d", math.floor(player.credits * 0.9)), 10, 30, 12)
	end
end

function renderPopUps()
	if (popUps == nil or newHighScore ~= nil) then return end

	for i, popUpItem in ipairs(popUps) do
		printPopUpBackground(i)
		for j, lineItem in ipairs(popUpItem) do
			print(lineItem, 8 + i * 4, 10 * j + i * 4 - 2, 0)
		end
	end
end

t=0

function TIC()
	if (not gameLoaded) then
		loadHighScores()
		newGame()
		gameLoaded = true
	end

	if (exitGame) then
		exit()
	end

	cls(0)
	renderPage()
	renderPopUps()
	renderHighScoreEntry()

	if (warp ~= nil and page == nil and (popUps == nil or #popUps == 0) and newHighScore == nil) then
		continueWarp()
	elseif btnp(0) then
		onButtonPress("up")
	elseif btnp(1) then
		onButtonPress("down")
	elseif btnp(2) then
		onButtonPress("left")
	elseif btnp(3) then
		onButtonPress("right")
	elseif btnp(4) then
		onButtonPress("a")
	elseif btnp(5) then
		onButtonPress("b")
	elseif btnp(6) then
		onButtonPress("x")
	elseif btnp(7) then
		onButtonPress("y")
	end

	t=t+1
end
